﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using StockFinder.StockLists;
using StockFinder.StockLists.Indexes;
using StockFinder.Indicators.Day.ClosePrice;
using StockFinder.YahooFinance;
using StockFinder.DataAccess;
using StockFinder.Model;
using System.Text;
using System.Web.UI.HtmlControls;
using System.Drawing;

public partial class RsiFilter : System.Web.UI.Page
{
    protected void Page_Load(object sender, EventArgs e)
    {

    }
    protected void _RunButton_Click(object sender, EventArgs e)
    {
        //1 get stocklists
        var stockLists = new List<IStockList>{
            new TelegraphOnlineFtse100StockList(){ LoadPrices = false},
            new TelegraphOnlineFtse250StockList(){ LoadPrices = false},
            new FinvizOnlineDowJonesStockList(){ LoadPrices = false},
            new FinvizOnlineSnP500StockList(){ LoadPrices = false}};

        //2 get filter criteria
        var priceHistoryInYears = Convert.ToInt32(_PriceHistoryTextbox.Text);
        var rsiLookbackPeriod = Convert.ToInt32(_RsiLookbackPeriodTextbox.Text);
        var rsiOversoldFilter = Convert.ToDecimal(_RsiFilterTextbox.Text);
        var priceOversoldFilter = Convert.ToDecimal(_PriceOversoldTextbox.Text);

        //3 set up 
        string indicatorName = string.Format("RSI_{0}", rsiLookbackPeriod);
        var rsi = new ExponentialMovingAverageWilderRelativeStrengthIndexClosePriceDayIndicator(rsiLookbackPeriod, indicatorName); 
        var fromDate = DateTime.Today.AddYears(-1 * priceHistoryInYears);
        StringBuilder output = new StringBuilder();        
        var pricesDownloader = new YahooFinanceOnlineStockPriceHistoryDownloader();
        var pricesCsvExtractor = new YahooFinanceCsvStockPriceHistoryExtractor();


        output.AppendLine("Symbol,RSI,%offHigh,Index,PassedFilter");
        _ResultsTable.Rows.Clear();

        var headerRow = new TableHeaderRow();
        headerRow.TableSection = TableRowSection.TableHeader;
        AddTableHeaderCell(headerRow, "Symbol");
        AddTableHeaderCell(headerRow, "Rsi");
        AddTableHeaderCell(headerRow, "% off high");
        AddTableHeaderCell(headerRow, "Stocklist");
        AddTableHeaderCell(headerRow, "Passed filter");

        _ResultsTable.Rows.Add(headerRow);

        //4 loop stocklists
        using (DailyPriceDataAccess dataAccess = new DailyPriceDataAccess())
        {
            List<DailyPrice> prices = null;
            foreach (IStockList stockList in stockLists)
            {
                foreach (var symbol in stockList)
                {
                    if (symbol.Exchange == StockFinder.Model.Enumerations.Exchange.LONDON)
                    {
                        symbol.Name += ".L";
                    }

                    prices = dataAccess.GetAllDailyPricesBySymbolNameFromDate(symbol, fromDate);

                    if (prices == null)
                    {
                        //download and update prices
                        var pricesCsv = pricesDownloader.DownloadSymbolPricesCsv(symbol, fromDate, DateTime.Today);
                        if (string.IsNullOrEmpty(pricesCsv))
                        {
                            //something wrong downloading this stock
                            continue;
                        }
                        prices = pricesCsvExtractor.GetHistoricPricesFromSource(pricesCsv);
                    }

                    if (prices.Count == 0)
                    {
                        //download and update prices
                        var pricesCsv = pricesDownloader.DownloadSymbolPricesCsv(symbol, fromDate, DateTime.Today);
                        if (string.IsNullOrEmpty(pricesCsv))
                        {
                            //something wrong downloading this stock
                            continue;
                        }
                        prices = pricesCsvExtractor.GetHistoricPricesFromSource(pricesCsv);
                    }

                    rsi.ApplyIndicator(prices);

                    var price = prices.First();

                    //_Log.DebugFormat("Getting highest close");

                    var highestClose = prices.Max(p => p.AdjustedClose);

                    //_Log.DebugFormat("Calculating percent off high");

                    var percentOffHigh = ((highestClose - price.AdjustedClose) / highestClose) * 100;

                    //_Log.DebugFormat("Applying filter");

                    try
                    {
                        bool passedFilter = percentOffHigh >= priceOversoldFilter &&
                        price.DayIndicators[indicatorName] < rsiOversoldFilter;                        

                        var row = new TableRow();
                        AddTableCell(row, symbol.Name);
                        AddTableCell(row, Math.Round(price.DayIndicators[indicatorName], 2).ToString());
                        AddTableCell(row, Math.Round(percentOffHigh, 2).ToString());
                        AddTableCell(row, stockList.Name);
                        AddTableCell(row, passedFilter.ToString());

                        if (passedFilter)
                        {
                            row.BackColor = Color.Green;
                        }

                        _ResultsTable.Rows.Add(row);                        
                    }
                    catch (Exception exception)
                    {
                        //_Log.Error(exception.ToString());
                    }
                }
            }
        }
    }

    private void AddTableCell(TableRow row, string text)
    {
        var cell = new TableCell();

        row.Cells.Add(cell);

        cell.Text = text;
    }

    private void AddTableHeaderCell(TableHeaderRow row, string text)
    {
        var cell = new TableHeaderCell();

        row.Cells.Add(cell);

        cell.Text = text;
    }
}